package com.htl.exampro.course.service.impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.htl.exampro.base.exception.ExamProException;
import com.htl.exampro.base.utils.UserUtil;
import com.htl.exampro.course.mapper.CourseMapper;
import com.htl.exampro.course.mapper.CourseSelectionMapper;
import com.htl.exampro.course.pojo.domain.CourseDO;
import com.htl.exampro.course.pojo.domain.CourseSelectionDO;
import com.htl.exampro.course.pojo.vo.CourseSelectionVO;
import com.htl.exampro.course.pojo.vo.CourseVO;
import com.htl.exampro.course.service.CourseSelectionService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;

/**
 * <p>
 * 用户选课关联表 服务实现类
 * </p>
 *
 * @author hehehe
 * @since 2025-05-26
 */
@Service
public class CourseSelectionServiceImpl extends ServiceImpl<CourseSelectionMapper, CourseSelectionDO>
        implements CourseSelectionService {

    @Autowired
    private CourseMapper courseMapper;


    @Override
    public List<CourseVO> getCoursesByUser(Long userId) {
        List<CourseSelectionDO> courseSelectionDOS = this.lambdaQuery().select(CourseSelectionDO::getCourseId)
                .eq(CourseSelectionDO::getUserId, userId)
                .list();
        List<Long> courseIds = courseSelectionDOS.stream().map(CourseSelectionDO::getCourseId).toList();
        List<CourseDO> courseDOS = courseMapper.selectByIds(courseIds);

        return BeanUtil.copyToList(courseDOS, CourseVO.class);
    }

    @Override
    public List<CourseSelectionVO> getUsersByCourse(Long courseId) {
        List<CourseSelectionDO> courseSelectionDOS = this.lambdaQuery()
                .eq(CourseSelectionDO::getCourseId, courseId)
                .list();
        return BeanUtil.copyToList(courseSelectionDOS, CourseSelectionVO.class);
    }

    @Override
    @Transactional
    public Integer selectCourse(Long courseId) {
        CourseDO course = courseMapper.selectCourseForUpdate(courseId);
        if (course == null || course.getStatus() != 1 || !course.getIsPublic()) {
            ExamProException.cast(403, "课程不可选,课程状态非活跃或未公开");
        }
        int current = baseMapper.countByCourseId(courseId);
        if (current >= course.getMaxStudents()) {
            ExamProException.cast(429, "课程人数已满, 当前课程最大容量" + course.getMaxStudents() + "人，已选满");
        }
        Long userId = Long.valueOf(UserUtil.getUserId());
        if (baseMapper.existsByUserIdAndCourseId(userId, courseId)) {
            ExamProException.cast(409, "重复选课, 已选过该课程");
        }
        CourseSelectionDO selection = new CourseSelectionDO();
        selection.setUserId(userId);
        selection.setCourseId(courseId);
        return baseMapper.insert(selection);
    }

    @Override
    @Transactional
    public Integer cancelSelection(Long selectionId) {
        CourseSelectionDO selection = baseMapper.selectById(selectionId);
        if (selection == null || Boolean.TRUE.equals(selection.getIsDeleted())) {
            ExamProException.cast(404, "选课记录不存在");
        }
        Long userId = Long.valueOf(UserUtil.getUserId());
        if (!selection.getUserId().equals(userId)) {
            ExamProException.cast(403, "无权操作");
        }
        CourseDO course = courseMapper.selectById(selection.getCourseId());
        if (course.getStartTime().isBefore(LocalDateTime.now())) {
            ExamProException.cast(400, "开课后不可退课");
        }
        return baseMapper.deleteById(selection);
    }

}
